<?php

require '../vendor/autoload.php';


class MathExpressionEvaluator {
    public function evaluate($expression) {
        $tokens = $this->tokenize($expression);
        $result = $this->parseExpression($tokens);
        return $result;
    }

    private function tokenize($expression) {
        $pattern = '/(\d+|\+|\-|\*|\/|\(|\))/';
        preg_match_all($pattern, $expression, $matches);
        return $matches[0];
    }

    private function parseExpression(&$tokens) {
        $values = [];
        $operators = [];

        while (count($tokens) > 0) {
            $token = array_shift($tokens);

            if (is_numeric($token)) {
                $values[] = $token;
            } elseif ($token === '(') {
                $values[] = $this->parseExpression($tokens);
            } elseif ($token === ')') {
                break;
            } else {
                while (count($operators) > 0 && $this->precedence($operators[count($operators) - 1]) >= $this->precedence($token)) {
                    $this->applyOperator(array_pop($operators), $values);
                }
                $operators[] = $token;
            }
        }

        while (count($operators) > 0) {
            $this->applyOperator(array_pop($operators), $values);
        }

        return array_pop($values);
    }

    private function precedence($operator) {
        if ($operator === '+' || $operator === '-') return 1;
        if ($operator === '*' || $operator === '/') return 2;
        return 0;
    }

    private function applyOperator($operator, &$values) {
        $right = array_pop($values);
        $left = array_pop($values);

        switch ($operator) {
            case '+':
                $values[] = $left + $right;
                break;
            case '-':
                $values[] = $left - $right;
                break;
            case '*':
                $values[] = $left * $right;
                break;
            case '/':
                if ($right == 0) throw new Exception('Division by zero');
                $values[] = $left / $right;
                break;
        }
    }
}

// Usage
try {
    $evaluator = new MathExpressionEvaluator();
    $expression = '3+1*0+8/4';
    $result = $evaluator->evaluate($expression);
    echo "Result: " . $result;
} catch (Exception $e) {
    echo "Error: " . $e->getMessage();
}
?>
